package com.maistars.spider.service.parser;

import com.alibaba.fastjson.JSONObject;
import com.maistars.spider.common.constants.PageContentType;
import com.maistars.spider.service.parser.policy.ParserPolicy;
import com.maistars.spider.service.parser.policy.ParserPolicyType;
import com.maistars.spider.service.parser.policy.impl.ConstPolicy;
import com.maistars.spider.service.parser.policy.impl.JsonPathPolicy;
import com.maistars.spider.service.parser.policy.impl.XPathPolicy;
import com.maistars.spider.service.parser.policy.impl.XmlPathPolicy;
import com.maistars.spider.service.domain.rule.FieldRule;
import com.maistars.spider.service.parser.policy.*;
import com.maistars.spider.service.process.html.HtmlProcessorPipeline;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author dhr
 * @date 2021/1/17 上午12:45
 */
public class FieldRuleParser {

    private Map<Integer, ParserPolicy> parserPolicyManager = new HashMap<>();

    private List<FieldRule> fieldRules = new ArrayList<>();

    private String pageContent;

    private int pageContentType;

    public FieldRuleParser(List<FieldRule> fieldRules, String pageContent, int pageContentType) {
        this.fieldRules = fieldRules;
        this.pageContentType = pageContentType;
        this.pageContent = pageContent;
        for (FieldRule fieldRule : fieldRules) {
            if (fieldRule.getParseType() == ParserPolicyType.XPATH.getValue()) {
                ParserPolicy parserPolicy = new XPathPolicy();
                parserPolicy.init(pageContent);
                parserPolicyManager.put(fieldRule.getParseType(), parserPolicy);
            } else if (fieldRule.getParseType() == ParserPolicyType.JSONPATH.getValue()) {
                ParserPolicy parserPolicy = new JsonPathPolicy();
                parserPolicy.init(pageContent);
                parserPolicyManager.put(fieldRule.getParseType(), parserPolicy);
            } else if (fieldRule.getParseType() == ParserPolicyType.XMLPATH.getValue()) {
                ParserPolicy parserPolicy = new XmlPathPolicy();
                parserPolicy.init(pageContent);
                parserPolicyManager.put(fieldRule.getParseType(), parserPolicy);
            } else if (fieldRule.getParseType() == ParserPolicyType.CONSTPATH.getValue()) {
                ParserPolicy parserPolicy = new ConstPolicy();
                parserPolicy.init(pageContent);
                parserPolicyManager.put(fieldRule.getParseType(), parserPolicy);
            }
        }
    }

    public Map<FieldRule, List<String>> parse() {
        Map<FieldRule, List<String>> result = new HashMap<>();
        for (FieldRule fieldRule : fieldRules) {
            if (PageContentType.HTML.getValue() == pageContentType && ParserPolicyType.XPATH.getValue() == fieldRule.getParseType()) {
                JSONObject processorConfig = new JSONObject();
                if(!result.containsKey(fieldRule)){
                    result.put(fieldRule,new ArrayList<>());
                }
                List<String> fieldRuleParseResult = HtmlProcessorPipeline.build(0,processorConfig,fieldRule,pageContent)
                            .execute();
                if(fieldRuleParseResult != null){
                    result.get(fieldRule).addAll(fieldRuleParseResult);
                }
            }else{
                ParserPolicy parserPolicy = parserPolicyManager.get(fieldRule.getParseType());
                result.put(fieldRule, parserPolicy.execute(fieldRule.getRule(), new HashMap<>()));
            }
        }
        return result;
    }

}
